---
title: Guide Documents > Core Library > TypedParam
---
import { Callout, Tabs } from 'nextra/components'

## Outline
```typescript filename="@nestia/core" showLineNumbers
export function TypedParam(name: string): ParameterDecorator;
```

Type safe path parameter decorator.

`@TypedParam()` is a decorator parsing path parameter. 

It's almost same with original `@Param()` function of `NestJS`, however, `@TypedParam()` is more type safe. 

As `@TypedParam()` can analyze source code in the compilation level, it can specify parameter type by itself. Also, while `NestJS` cannot distinguish `nullable` type and consider every parameter value as a `string` type, `@TypedParam()` can do it. Furthermore, `@TypedParam()` can validate special types like `"uuid"` or `"date"`.

Let's read below example code, and see how `@TypedParam()` works.

<Callout type="warning">

`@TypedParam()` is not essential for [Swagger Documents](./sdk/swagger) or [SDK Library](./sdk/sdk) building.

Therefore, it is not a matter to use `@TypedParam()` or `@Param()` of the original NestJS.

</Callout>




## How to use
<Tabs 
  items={[
    <code>ParametersController.ts</code>, 
    'Compiled JavaScript File',
  ]}>
  <Tabs.Tab>
```typescript copy filename="ParametersController.ts" showLineNumbers {9, 16, 23}
import { TypedParam } from "@nestia/core";
import { Controller, Get } from "@nestjs/common";
import { tags } from "typia";

@Controller("parameters")
export class ParametersController {
  @Get("uint32/:value")
  public async uint32(
    @TypedParam("value") value: (number & tags.Type<"uint32">) | null,
  ): Promise<(number & tags.Type<"uint32">) | null> {
    return value;
  }

  @Get("string/:value")
  public async string(
    @TypedParam("value") value: string
  ): Promise<string> {
    return value;
  }

  @Get("uuid/:value")
  public async uuid(
    @TypedParam("value") value: string & tags.Format<"uuid">,
  ): Promise<string> {
    return value;
  }
}
```
  </Tabs.Tab>
  <Tabs.Tab>
```javascript filename="ParametersController.js" showLineNumbers {46-53, 59-66, 72-79}
"use strict";
var __decorate =
  (this && this.__decorate) ||
  function (decorators, target, key, desc) {
    var c = arguments.length,
      r =
        c < 3
          ? target
          : desc === null
          ? (desc = Object.getOwnPropertyDescriptor(target, key))
          : desc,
      d;
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function")
      r = Reflect.decorate(decorators, target, key, desc);
    else
      for (var i = decorators.length - 1; i >= 0; i--)
        if ((d = decorators[i]))
          r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
    return c > 3 && r && Object.defineProperty(target, key, r), r;
  };
var __metadata =
  (this && this.__metadata) ||
  function (k, v) {
    if (typeof Reflect === "object" && typeof Reflect.metadata === "function")
      return Reflect.metadata(k, v);
  };
var __param =
  (this && this.__param) ||
  function (paramIndex, decorator) {
    return function (target, key) {
      decorator(target, key, paramIndex);
    };
  };
var __awaiter =
  (this && this.__awaiter) ||
  function (thisArg, _arguments, P, generator) {
    function adopt(value) {
      return value instanceof P
        ? value
        : new P(function (resolve) {
            resolve(value);
          });
    }
    return new (P || (P = Promise))(function (resolve, reject) {
      function fulfilled(value) {
        try {
          step(generator.next(value));
        } catch (e) {
          reject(e);
        }
      }
      function rejected(value) {
        try {
          step(generator["throw"](value));
        } catch (e) {
          reject(e);
        }
      }
      function step(result) {
        result.done
          ? resolve(result.value)
          : adopt(result.value).then(fulfilled, rejected);
      }
      step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
  };
Object.defineProperty(exports, "__esModule", { value: true });
exports.ParametersController = void 0;
const core_1 = require("@nestia/core");
const common_1 = require("@nestjs/common");
let ParametersController = class ParametersController {
  uint32(value) {
    return __awaiter(this, void 0, void 0, function* () {
      return value;
    });
  }
  string(value) {
    return __awaiter(this, void 0, void 0, function* () {
      return value;
    });
  }
  uuid(value) {
    return __awaiter(this, void 0, void 0, function* () {
      return value;
    });
  }
};
exports.ParametersController = ParametersController;
__decorate(
  [
    (0, common_1.Get)("uint32/:value"),
    __param(
      0,
      (0, core_1.TypedParam)("value", {
        name: '((number & Type<"uint32">) | null)',
        is: (input) => {
          return (
            null === input ||
            ("number" === typeof input &&
              Math.floor(input) === input &&
              0 <= input &&
              input <= 4294967295)
          );
        },
        cast: (str) => ("null" === str ? null : Number(str)),
      }),
    ),
    __metadata("design:type", Function),
    __metadata("design:paramtypes", [Object]),
    __metadata("design:returntype", Promise),
  ],
  ParametersController.prototype,
  "uint32",
  null,
);
__decorate(
  [
    (0, common_1.Get)("string/:value"),
    __param(
      0,
      (0, core_1.TypedParam)("value", {
        name: "string",
        is: (input) => {
          return "string" === typeof input;
        },
        cast: (str) => str,
      }),
    ),
    __metadata("design:type", Function),
    __metadata("design:paramtypes", [String]),
    __metadata("design:returntype", Promise),
  ],
  ParametersController.prototype,
  "string",
  null,
);
__decorate(
  [
    (0, common_1.Get)("uuid/:value"),
    __param(
      0,
      (0, core_1.TypedParam)("value", {
        name: '(string & Format<"uuid">)',
        is: (input) => {
          return (
            "string" === typeof input &&
            /^(?:[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}|00000000-0000-0000-0000-000000000000)$/i.test(
              input,
            )
          );
        },
        cast: (str) => str,
      }),
    ),
    __metadata("design:type", Function),
    __metadata("design:paramtypes", [Object]),
    __metadata("design:returntype", Promise),
  ],
  ParametersController.prototype,
  "uuid",
  null,
);
exports.ParametersController = ParametersController = __decorate(
  [(0, common_1.Controller)("parameters")],
  ParametersController,
);
```
  </Tabs.Tab>
</Tabs>

Just call `@TypedParam()` function on the path parameter, that's all.

If you want to special parameter type like `"uint32"` or `"uuid"`, utilize [type tags of `typia`](https://typia.io/docs/validators/tags).

When wrong typed value comes, 400 bad request error would be thrown.




## Restriction
`@TypedParam()` allows only atomic type.

  - `boolean`
  - `number`
  - `string`
  - `bigint`

Also, `@TypedParam()` allows nullable like `number | null`, but undefindable type is not.

  - `number | null` is allowed
  - `string | undefined` is prohibited

If you violate above condition, and try to declare object or union type, compilation error would be occurred:

```bash
Error on nestia.core.TypedParam(): only atomic type is allowed
```